package com.zyy.jomap.back;

import com.zyy.jomap.resolve.GenerateMapFile;

import java.io.File;
import java.io.FileFilter;
import java.net.JarURLConnection;
import java.net.URL;
import java.net.URLDecoder;
import java.util.Enumeration;
import java.util.HashSet;
import java.util.Set;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;

/**
 * OK
 *
 * @author zhangyy
 */
public class MatchJava {

    private static Set<String> classStrSet = new HashSet<>();
    private static String resolveClassBuffer="";
    public static void doMatchJava() {
        Set<Class<?>> classSet = new HashSet<Class<?>>();

        //"com.zyy.jomap.bo"  file;
        //"com.hoolink.iot.common.server.device.dmx"  jar;
        //"com.baomidou.mybatisplus.core.metadata"  jar;
        //"com.zyy.yjomapdemo.bo"  无法使用该方式加载;
        //String packageName ="com.hoolink.iot.common.server.device.dmx";
        String packageName ="com.hoolink.iot.common.server.device.dmx";
        addBuffer("execute","MathJava->doMatchJava");
        try {
            Enumeration<URL> urls = MatchJava.class.getClassLoader().getResources(packageName.replace(".", "/"));
            addBuffer("java urls hasMoreElements",urls.hasMoreElements()+"");
            while (urls.hasMoreElements()) {
                URL url = urls.nextElement();
                addBuffer("java url",url.toString());
                if (url != null) {
                    String protocol = url.getProtocol();
                    if (protocol.equals("file")) {
                        // 转码
                        String packagePath = URLDecoder.decode(url.getFile(), "UTF-8");
                        addBuffer("packagePath url",packagePath);
                        // 添加
                        addClass(classSet, packagePath, packageName);
                    } else if (protocol.equals("jar")) {
                        JarURLConnection jarURLConnection = (JarURLConnection) url.openConnection();
                        if (jarURLConnection != null) {
                            JarFile jarFile = jarURLConnection.getJarFile();
                            if (jarFile != null) {
                                Enumeration<JarEntry> jarEntries = jarFile.entries();
                                while (jarEntries.hasMoreElements()) {
                                    JarEntry jarEntry = jarEntries.nextElement();
                                    String jarEntryName = jarEntry.getName();
                                    if (jarEntryName.endsWith(".class")) {
                                        String className = jarEntryName.substring(0, jarEntryName.lastIndexOf("."))
                                                .replaceAll("/", ".");
                                        doAddClass(classSet, className);
                                        doAddClassStr(classStrSet,className);
                                        //addBuffer("jar java class",className);
                                    }
                                }
                            }
                        }
                    }
                }
            }
            addBuffer("resolve java file name",classStrSet.toString());
            addBuffer("resolve class",classSet.toString());
        }catch(Exception e){
            e.printStackTrace();
            addBuffer("error",e.getMessage());
        }finally {
            GenerateMapFile.doGenerateClassFile(resolveClassBuffer,"com.zyy.jomap.convert.test");
        }
    }

    /**
     * 添加文件到SET集合
     * @Title: addClass
     * @Description: TODO(这里用一句话描述这个方法的作用)
     * @param @param classSet
     * @param @param packagePath
     * @param @param packageName    设定文件
     * @return void    返回类型
     * @throws
     */
    private static void addClass(Set<Class<?>> classSet, String packagePath, String packageName) {
        addBuffer("packagePath",packagePath);
        addBuffer("packageName",packageName);
        File[] files = new File(packagePath).listFiles(new FileFilter() {
            @Override
            public boolean accept(File file) {
                return (file.isFile() && file.getName().endsWith(".class") || file.isDirectory());
            }
        });
        for (File file : files) {
            String fileName = file.getName();
            addBuffer("filePath",file.getAbsolutePath());
            addBuffer("fileName",file.getName());
            if (file.isFile()) {
                String className = fileName.substring(0, fileName.lastIndexOf("."));
                if (packageName!=null) {
                    className = packageName + "." + className;
                }
                // 添加
                doAddClass(classSet, className);
                doAddClassStr(classStrSet,className);
            } else {
                // 子目录
                String subPackagePath = fileName;
                if (packagePath!=null) {
                    subPackagePath = packagePath + "/" + subPackagePath;
                }

                String subPackageName = fileName;
                if (packageName!=null) {
                    subPackageName = packageName + "." + subPackageName;
                }
                addClass(classSet, subPackagePath, subPackageName);
            }
        }
    }

    private static void doAddClassStr(Set<String> classSet, String className) {
        Class<?> cls = null;
        classSet.add(className);
    }

    private static void doAddClass(Set<Class<?>> classSet, String className) {
        Class<?> cls = null;
        try {
            cls = MatchJava.class.getClassLoader().loadClass(className);
            classSet.add(cls);
        } catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }

    private static void addBuffer(String tip,String content){
        resolveClassBuffer+=tip+"==================>"+content+"\r\n";
    }
}
